import re

from base.constant import EmptyValue


def is_stable_name(ip):
    ip_match = r"^(?:(?:25[0-5]|2[0-4][0-9]|1[0-9][0-9]|0?[0-9]?[1-9]|0?[1-9]0)\.)(?:(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){2}(?:25[0-4]|2[0-4][0-9]|1[0-9][0-9]|0?[0-9]?[1-9]|0?[1-9]0)$"
    if re.match(ip_match, ip):
        # 分割IP地址
        octets = ip.split('.')
        first_octet = int(octets[0])
        second_octet = int(octets[1])
        # 判断是否是本地地址
        if ip == "10.28.0.0" or ip.startswith("10.28.0.") or ip.startswith("10.28.0.0/16"):
            return "LOCAL_ADDRESS"
        # 判断是否是VPN地址
        if ip.startswith("10.28.15"):
            return "VPN_ADDRESS"
        # 判断是否是分支机构地址
        if (192 <= first_octet <= 195) or (first_octet == 192 and 144 <= second_octet <= 255):
            return "DEPARTMENT_ADDRESS"
    else:
        return False


def fill_geo_empty(value):
    if value == "" or value is None:
        return EmptyValue.IP_GEO_EMPTY.value
    else:
        return value


def get_geo_by_ip(reader, map):
    source_ip = map["source.ip"]
    source_ip_name = is_stable_name(source_ip)
    if not source_ip_name:
        try:
            response = reader.city(source_ip)
            map["source.ip_Country_IsoCode"] = fill_geo_empty(response.country.iso_code)
            map['source.ip_Country_Name'] = fill_geo_empty(response.country.name)
            map["source.ip_Country_SpecificName"] = fill_geo_empty(response.subdivisions.most_specific.name)
            map['source.ip_Country_SpecificIsoCode'] = fill_geo_empty(response.subdivisions.most_specific.iso_code)
            map['source.ip_City_Name'] = fill_geo_empty(response.city.name)
            map['source.ip_City_PostalCode'] = fill_geo_empty(response.postal.code)
            map['source.ip_Location_Latitude'] = fill_geo_empty(response.location.latitude)
            map["source.ip_Location_Longitude"] = fill_geo_empty(response.location.longitude)
        except Exception as e:
            map["source.ip_Country_IsoCode"] = EmptyValue.IP_GEO_EMPTY.value
            map['source.ip_Country_Name'] = EmptyValue.IP_GEO_EMPTY.value
            map["source.ip_Country_SpecificName"] = EmptyValue.IP_GEO_EMPTY.value
            map['source.ip_Country_SpecificIsoCode'] = EmptyValue.IP_GEO_EMPTY.value
            map['source.ip_City_Name'] = EmptyValue.IP_GEO_EMPTY.value
            map['source.ip_City_PostalCode'] = EmptyValue.IP_GEO_EMPTY.value
            map['source.ip_Location_Latitude'] = EmptyValue.IP_GEO_EMPTY.value
            map["source.ip_Location_Longitude"] = EmptyValue.IP_GEO_EMPTY.value
    else:
        map["source.ip_Country_IsoCode"] = source_ip_name
        map['source.ip_Country_Name'] = source_ip_name
        map["source.ip_Country_SpecificName"] = source_ip_name
        map['source.ip_Country_SpecificIsoCode'] = source_ip_name
        map['source.ip_City_Name'] = source_ip_name
        map['source.ip_City_PostalCode'] = source_ip_name
        map['source.ip_Location_Latitude'] = source_ip_name
        map["source.ip_Location_Longitude"] = source_ip_name
    destination_ip = map["destination.ip"]
    destination_ip_name = is_stable_name(destination_ip)
    if not destination_ip_name:
        try:
            response = reader.city(destination_ip)
            map["destination.ip_Country_IsoCode"] = fill_geo_empty(response.country.iso_code)
            map['destination.ip_Country_Name'] = fill_geo_empty(response.country.name)
            map["destination.ip_Country_SpecificName"] = fill_geo_empty(response.subdivisions.most_specific.name)
            map['destination.ip_Country_SpecificIsoCode'] = fill_geo_empty(response.subdivisions.most_specific.iso_code)
            map['destination.ip_City_Name'] = fill_geo_empty(response.city.name)
            map['destination.ip_City_PostalCode'] = fill_geo_empty(response.postal.code)
            map['destination.ip_Location_Latitude'] = fill_geo_empty(response.location.latitude)
            map["destination.ip_Location_Longitude"] = fill_geo_empty(response.location.longitude)
        except Exception as e:
            map["destination.ip_Country_IsoCode"] = EmptyValue.IP_GEO_EMPTY.value
            map['destination.ip_Country_Name'] = EmptyValue.IP_GEO_EMPTY.value
            map["destination.ip_Country_SpecificName"] = EmptyValue.IP_GEO_EMPTY.value
            map['destination.ip_Country_SpecificIsoCode'] = EmptyValue.IP_GEO_EMPTY.value
            map['destination.ip_City_Name'] = EmptyValue.IP_GEO_EMPTY.value
            map['destination.ip_City_PostalCode'] = EmptyValue.IP_GEO_EMPTY.value
            map['destination.ip_Location_Latitude'] = EmptyValue.IP_GEO_EMPTY.value
            map["destination.ip_Location_Longitude"] = EmptyValue.IP_GEO_EMPTY.value
    else:
        map["destination.ip_Country_IsoCode"] = destination_ip_name
        map['destination.ip_Country_Name'] = destination_ip_name
        map["destination.ip_Country_SpecificName"] = destination_ip_name
        map['destination.ip_Country_SpecificIsoCode'] = destination_ip_name
        map['destination.ip_City_Name'] = destination_ip_name
        map['destination.ip_City_PostalCode'] = destination_ip_name
        map['destination.ip_Location_Latitude'] = destination_ip_name
        map["destination.ip_Location_Longitude"] = destination_ip_name
    return map
